package storage

import (
    "fmt"
    "os"
    "path/filepath"
    "strings"
    "time"

    "github.com/samaa/photosalesplus/backend/internal/config"
)

const (
	VariantOriginal = "original"
	VariantPreview  = "preview"
)

func EnsureDirectories(cfg *config.Config) error {
    dirs := []string{
        cfg.StorageDir,
        filepath.Join(cfg.StorageDir, VariantOriginal),
        filepath.Join(cfg.StorageDir, VariantPreview),
    }

	for _, dir := range dirs {
		if err := os.MkdirAll(dir, 0o755); err != nil {
			return err
		}
	}

	return nil
}

// BuildDatedRelativePath returns a path relative to StorageDir like:
//   original/2006/01/02/filename.ext
func BuildDatedRelativePath(variant, filename string, at time.Time) string {
    yyyy, mm, dd := at.Format("2006"), at.Format("01"), at.Format("02")
    // guard against leading slashes in filename
    filename = strings.TrimLeft(filename, "/\\")
    return filepath.ToSlash(filepath.Join(variant, yyyy, mm, dd, filename))
}

// EnsureDirForRelative ensures the directory for a relative path exists.
func EnsureDirForRelative(cfg *config.Config, relativePath string) error {
    abs := filepath.Join(cfg.StorageDir, filepath.FromSlash(relativePath))
    dir := filepath.Dir(abs)
    return os.MkdirAll(dir, 0o755)
}

// AbsolutePath joins StorageDir with a relative path (using OS separators).
func AbsolutePath(cfg *config.Config, relativePath string) string {
    return filepath.Join(cfg.StorageDir, filepath.FromSlash(relativePath))
}

// BuildURL returns the public URL for a relative path under StorageDir.
func BuildURL(relativePath string) string {
    return fmt.Sprintf("/images/%s", strings.TrimLeft(filepath.ToSlash(relativePath), "/"))
}
